
#include <stdint.h>

#define PACKED __attribute__ ((packed))

typedef struct PACKED{
    char name[11];
    uint8_t att;
    uint8_t rev[10];
    uint16_t wtime;
    uint16_t wdate;
    uint16_t fst_clus;
    uint32_t fsize;
}root_dir_entry_t;

typedef struct load_data_t{
  uint8_t*  data;
  uint8_t*  end_data;
  int      (*update)(struct load_data_t*);
}load_data_t;

uint32_t time = 0;
int cur_clus = 0;
static int data_num = 0;
const char*clus_image = 0;
extern int FCB_AutoDecompressData(load_data_t*d);

static int get_fat12_clus(const uint8_t *img,int table){
    table *= 12;
    int word_pos = table>>5;
    int hi = (table&0x1f);
    uint32_t v = ((uint32_t*)(img + 512))[word_pos];
    v >>= hi;
    v &= 0xfff;
    return v;
}

static int update(load_data_t*d){
    if(data_num<=0)return 0;
    int c = get_fat12_clus(clus_image,cur_clus);
    if(c==0){
        return 0;
    }
    else if(c>0xff7){
        return 2;
    }
    cur_clus = c;
    d->data = clus_image + c * 512;
    if(data_num>512){
        d->end_data = 512;
        data_num -= 512;
    }
    else{
        d->end_data = data_num;
        data_num -= data_num;
    }
    return 1;
}

extern void board_load_fpga(load_data_t*dd);

void load_fpga_fat12_file(const root_dir_entry_t*rd,const uint8_t*img){
    if(rd->wtime==time){
        return;
    }
    if(rd->fsize<=0){
        return;
    }
    time = rd->wtime;
    load_data_t ld;
    cur_clus = rd->fst_clus + 1;
    clus_image = img;
    ld.data = img + cur_clus * 512;
    if(rd->fsize<512){
        ld.end_data = ld.data + rd->fsize;
    }
    else{
        ld.end_data = ld.data + 512;
    }
    ld.update = update;
    data_num = rd->fsize - 512;
    board_load_fpga(&ld);
}

void load_fpga_fat12(const uint8_t*fat12_img){
    uint8_t *fat12_table = fat12_img + 512 * 1;
    root_dir_entry_t *rd = fat12_img + 512 * 2;
    int i;
    for(i=0;i<16;i++){
        //一个扇区的大小
        if(i>0){
            if(rd->name[0]!=0xe5){
                if(
                    rd->name[8] =='B'&&
                    rd->name[9] =='I'&&
                    rd->name[10]=='N'&&
                    rd->fsize>0
                ){
                    load_fpga_fat12_file(rd,fat12_img);
                    break;
                }
            }
            else if(rd->name[0]==0)break;
        }
        rd++;
    }
}


